{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### 第18课：模型部署上线的几种服务发布方式"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "我们训练好的模型一般都是存储在内存中，这个时候就需要用到持久化方式，在 Python 中，常用的模型持久化方式有三种，并且都是以文件的方式持久化。\n",
    "\n",
    "## JSON（JavaScript Object Notation）格式。\n",
    "   * json.dumps：将 Python 对象编码成 JSON 字符串；\n",
    "   \n",
    "   * json.loads：将已编码的 JSON 字符串解码为 Python 对象。\n",
    "   "
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## pickle 模块\n",
    "       pickle 提供了一个简单的持久化功能。可以将对象以文件的形式存放在磁盘上。pickle 模块只能在 Python 中使用，Python 中几乎所有的数据类型（列表、字典、集合、类等）都可以用 pickle 来序列化。pickle 序列化后的数据，可读性差，人一般无法识别。\n",
    "        pickle.dump(obj, file[, protocol])：序列化对象，并将结果数据流写入到文件对象中。参数 protocol 是序列化模式，默认值为0，表示以文本的形式序列化。protocol 的值还可以是1或2，表示以二进制的形式序列化。\n",
    "        pickle.load(file)：反序列化对象。将文件中的数据解析为一个 Python 对象"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "from sklearn.externals import joblib"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# joblib.dump(model, model_path)  #模型保存\n",
    "# joblib.load(model_path)  #模型加载"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# Flask 和 Bottle 微服务框架"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "Bottle 本身主要包含以下四个模块，依靠它们便可快速开发微 Web 服务：\n",
    "\n",
    "路由（Routing）：将请求映射到函数，可以创建十分优雅的 URL；\n",
    "模板（Templates）：可以快速构建 Python 内置模板引擎，同时还支持 Mako、Jinja2、Cheetah 等第三方模板引擎；\n",
    "工具集（Utilites）：用于快速读取 form 数据，上传文件，访问 Cookies，Headers 或者其它 HTTP 相关的 metadata；\n",
    "服务器（Server）：内置 HTTP 开发服务器，并且支持 paste、fapws3、 bjoern、Google App Engine、Cherrypy 或者其它任何 WSGI HTTP 服务器。"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {},
   "outputs": [
    {
     "name": "stderr",
     "output_type": "stream",
     "text": [
      " * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit)\n",
      "127.0.0.1 - - [17/Feb/2019 14:37:53] \"\u001b[37mGET / HTTP/1.1\u001b[0m\" 200 -\n",
      "127.0.0.1 - - [17/Feb/2019 14:37:53] \"\u001b[33mGET /favicon.ico HTTP/1.1\u001b[0m\" 404 -\n"
     ]
    }
   ],
   "source": [
    "from flask import Flask\n",
    "app = Flask(__name__)\n",
    "\n",
    "@app.route('/')\n",
    "def hello_world():\n",
    "    return 'Hello World!'\n",
    "\n",
    "if __name__ == '__main__':\n",
    "    app.run()"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "from sklearn.externals import joblib\n",
    "model_path = \"../data/18/model.pkl\"\n",
    "model = joblib.load(model_path)\n",
    "sen =[[['坚决', 'a', 'ad', '1_v'],\n",
    "           ['惩治', 'v', 'v', '0_Root'],\n",
    "           ['贪污', 'v', 'v', '1_v'],\n",
    "           ['贿赂', 'n', 'n', '-1_v'],\n",
    "           ['等', 'u', 'udeng', '-1_v'],\n",
    "           ['经济', 'n', 'n', '1_v'],\n",
    "           ['犯罪', 'v', 'vn', '-2_v']]]\n",
    "print(model.predict(sen))"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "from sklearn.externals import joblib\n",
    "    from flask import Flask,request\n",
    "    app = Flask(__name__)\n",
    "\n",
    "    @app.route('/')\n",
    "    def hello_world():\n",
    "        return 'Hello World!'\n",
    "\n",
    "    @app.route('/predict/<sen>')\n",
    "    def predict(sen):\n",
    "        result = model.predict(sen)\n",
    "        return str(result)\n",
    "\n",
    "    if __name__ == '__main__':\n",
    "        model_path = \"../data/18/model.pkl\"\n",
    "        model = joblib.load(model_path)\n",
    "        app.run(host='localhost')"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "TensorFlow Serving 是一个用于机器学习模型 Serving 的高性能开源库。它可以将训练好的机器学习模型部署到线上，使用 gRPC 作为接口接受外部调用。更加让人眼前一亮的是，它支持模型热更新与自动模型版本管理。这意味着一旦部署 TensorFlow Serving 后，你再也不需要为线上服务操心，只需要关心你的线下模型训练。\n",
    "\n",
    "同样，TensorFlow Serving 可以将模型部署在移动端，如安卓或者 iOS 系统的 App 应用上。"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": null,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": []
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.6.8"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
